import gradio as gr
import pandas as pd
import logging
from .UserManage import UserManager
from .utils import sha256_js

class UserManageServer():
    def __init__(self, server_name = "0.0.0.0", server_port = 7862):
        self.user_data = None
        self.server_name = server_name
        self.server_port = server_port
        # 用户认证
        self.user_manager = UserManager()
        # 自定义JavaScript代码，用于在发送前处理密码
        self.login_js = """
        function preprocessLogin(username, password) {
            // 使用SHA-256对密码进行哈希处理
            if(username.trim() === "" || password.trim() === ""){
            return [null, null]
            }
            const hashHex = sha256(password);
            return [username, hashHex];
        }
        """
        self.add_user_js = """
        function preprocessLogin(username, password, remark, permission) {
            // 使用SHA-256对密码进行哈希处理
            if(username.trim() === "" || password.trim() === ""){
            return [null, null]
            }
            console.log(username, password, remark, permission);
            const hashHex = sha256(password);
            console.log(username, hashHex, remark, permission);
            return [username, hashHex, remark, permission];
            }
        """
        self.logger = logging.getLogger(__name__)

    def process_hashed_login(self, user_name, hashed_password):
        """账号密码认证"""
        # 账号密码是否未空
        if not user_name or not hashed_password:  # 账号或密码为空
            raise gr.Error("账号或密码为空！",print_exception=False)
        # 实际验证逻辑
        ok, permission, _ = self.user_manager.authenticate(user_name, hashed_password)
        if not ok:
            raise gr.Error("用户名或密码错误！",print_exception=False)
        # 判断用户权限 1 为管理员权限 2 为普通权限
        if permission == 1:
            return gr.update(visible=False), gr.update(visible=True)
        else:
            raise gr.Error("您没有管理员权限！", print_exception=False)
    
    def add_user(self, user_name, user_pwd, user_remark, user_permission):
        if user_name is None or user_pwd is None:
            return
        user_permission = self.user_manager.permission_map[user_permission]
        if not user_permission in (1,2):
            self.logger.info("新增用户权限设置错误！")
            return
        # 添加用户
        ok, msg = self.user_manager.add_user(user_name, user_pwd, user_remark, user_permission)
        # 添加用户成功
        if ok:
            gr.Info(f"{user_name} 用户添加成功！")
        else:
            self.logger.info(f"{user_name} {msg}")
            raise gr.Error(f"{user_name} {msg}", print_exception=False)

    def find_user(self, user_name:str):
        if len(user_name) ==0 or user_name is None:
            return gr.update(visible=False), gr.update(value=""), gr.update(value=""), gr.update(value="")
        # 查找用户信息
        user_info = self.user_manager.get_user_data(user_name)
        if len(user_info) == 0 or user_info is None:
            gr.Info(f"{user_name} 用户不存在")
            return gr.update(visible=False), gr.update(value=""), gr.update(value=""), gr.update(value="")
        user_remark = user_info[0]["remark"]
        user_permission = "管理员" if user_info[0]["permission"] == 1 else "普通用户"
        return gr.update(visible=True),gr.update(value=user_name), gr.update(value=user_remark), gr.update(value=user_permission)

    def delete_user(self, user_name):
        ok = self.user_manager.delete_user(user_name)
        if ok:
            gr.Info(f"{user_name} 删除成功！")
            return gr.update(visible=False), gr.update(value=""),gr.update(value=""),gr.update(value="")
        else:
            raise gr.Error(f"{user_name} 删除失败！",print_exception=False)

    def reset_user_pwd(self, user_name, new_user_pwd):
        ok  = self.user_manager.modify_pwd(user_name, new_user_pwd)
        if ok:
            gr.Info(f"{user_name} 密码重置完成！")
        else:
            raise gr.Error(f"{user_name} 密码重置失败！", print_exception=False)

    def load_all_user_data(self):
        # 选中该标签，加载数据
        all_user_data = self.user_manager.get_user_data()
        self.user_data = pd.DataFrame(all_user_data, dtype=str)
        self.user_data.loc[:,"permission"] = self.user_data.loc[:,"permission"].apply(lambda x: self.user_manager.permission_map[int(x)])
        self.user_data.columns = ["用户名","备注","权限","创建时间"]
        return gr.update(value = self.user_data)
    def create_interface(self):
        with gr.Blocks(head=sha256_js) as demo:
            # 用户管理界面
            with gr.Column(visible=False) as user_manager:
                gr.Markdown("## 用户管理页面")
                with gr.Tab("添加用户"):
                    add_user_name = gr.Textbox(placeholder="用户名",type="text",max_lines=1,show_label=False)
                    add_user_pwd = gr.Textbox(placeholder="密码",type="password",max_lines=1,show_label=False)
                    add_user_remark = gr.Textbox(placeholder="备注",type="text",max_lines=1,show_label=False)
                    add_user_permission = gr.Dropdown(["管理员","普通用户"],interactive=True,value="普通用户",show_label=False)
                    add_btn = gr.Button("添加用户")
                    add_btn.click(
                        fn=self.add_user,
                        inputs=[add_user_name, add_user_pwd, add_user_remark, add_user_permission],
                        js=self.add_user_js
                    )

                with gr.Tab("删除用户"):
                    with gr.Column(elem_id="delete_items", visible=False) as delete_user_info:
                        with gr.Row(elem_id="delete_info"):
                            delete_user_name = gr.Textbox(placeholder="用户名",type="text",max_lines=1,show_label=False,interactive=False,scale=1)
                            delete_user_remark = gr.Textbox(placeholder="备注",type="text",max_lines=1,show_label=False,interactive=False,scale=3)
                            delete_user_permission = gr.Textbox(placeholder="权限",type="text",max_lines=1,show_label=False,interactive=False,scale=1)
                        delete_btn = gr.Button("删除",elem_id="delete_button")
                        delete_btn.click(
                            fn=self.delete_user,
                            inputs=delete_user_name,
                            outputs=[delete_user_info, delete_user_name, delete_user_remark, delete_user_permission]
                        )
                    find_user_name = gr.Textbox(placeholder="用户名",type="text",max_lines=1,show_label=False)
                    find_btn = gr.Button("查找")
                    find_btn.click(
                        fn=self.find_user,
                        inputs=find_user_name,
                        outputs=[delete_user_info, delete_user_name, delete_user_remark, delete_user_permission]
                    )

                with gr.Tab("所有用户信息") as modify_tab:
                    table = gr.DataFrame(self.user_data, interactive=False, static_columns=[0],show_search="search",show_row_numbers=True, row_count=[0,"fixed"],col_count=[0,"fixed"],elem_id="show_user_table")
                # 加载用户
                modify_tab.select(
                    fn = self.load_all_user_data,
                    outputs=table
                )


                with gr.Tab("重置密码"):
                    with gr.Column(visible=False) as reset_user_pwd:
                        with gr.Row():
                            reset_user_name = gr.Textbox(placeholder="用户名",type="text",max_lines=1,show_label=False,interactive=False,scale=1)
                            reset_user_remark = gr.Textbox(placeholder="备注",type="text",max_lines=1,show_label=False,interactive=False,scale=3)
                            reset_user_permission = gr.Textbox(placeholder="权限",type="text",max_lines=1,show_label=False,interactive=False,scale=1)
                        new_pwd = gr.Textbox(placeholder="新密码",type="text",max_lines=1,show_label=False,interactive=True,scale=1)
                        delete_btn = gr.Button("重置密码")
                        delete_btn.click(
                            fn=self.reset_user_pwd,
                            js=self.login_js,
                            inputs=[reset_user_name, new_pwd]
                        )

                    find_user_name = gr.Textbox(placeholder="用户名",type="text",max_lines=1,show_label=False)
                    find_btn = gr.Button("查找")
                    find_btn.click(
                        fn=self.find_user,
                        inputs=find_user_name,
                        outputs=[reset_user_pwd, reset_user_name, reset_user_remark, reset_user_permission]
                    )

            # 登录界面
            with gr.Column(visible=True, elem_id="login_column",min_width=300) as column:
                username = gr.Textbox(label="用户名", placeholder="请输入用户名",max_length=80)
                password = gr.Textbox(label="密码", placeholder="请输入密码", type="password",max_length=80)
                login_btn = gr.Button("登录", variant="primary")
                # 添加自定义JavaScript
                login_btn.click(
                    fn=self.process_hashed_login,
                    inputs=[username, password],
                    js=self.login_js,
                    outputs=[column, user_manager]
                )

        return demo
    
    def run(self):
        demo = self.create_interface()
        demo.queue().launch(server_name=self.server_name, server_port=self.server_port)


if __name__ == "__main__":
    user_manager = UserManageServer()
    demo = user_manager.create_interface()
    demo.queue().launch()